{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Gradient Vanishing / Gradient Explosion"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## What happens when gradients vanish or explode?\n",
    "\n",
    "Remember that the neural network trains by using chain rules. That is, earlier layers' gradients are calculated by scaling later layers' gradients. Chain rule:\n",
    "\n",
    "$$\n",
    "\\frac{dy}{dx} = \\frac{df}{du} \\frac{du}{dx}\n",
    "$$\n",
    "\n",
    "If later layers gradients are extremely large, then it's going to scale the earlier gradients by a huge factor. Due to how the computer represent numbers, this number may just be `INFINITY`. If later layers gradients are extremely small, then it's going to scale down the earlier gradients a lot. The earlier gradients may just become `0` in such a case.\n",
    "\n",
    "In either cases, the gradients calculated are not true gradients, and may just make the network un-trainable. Do you really want to update your parameter by `INFINITY`?"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## When do gradients vanish or explode?\n",
    "\n",
    "In very deep networks, vanishing or explosion is more likely to happen. For example, if every layer scales the norm by 10 (not that big considering that there are many parameters in a layer), then after 300 layers (which is not uncommon in current neural networks), the gradients will approach `INFINITY`. The same arguments can be applied to vanishing gradients. In deep networks, these things happen quite often."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## How to deal with gradient vanishing or explosion?\n",
    "\n",
    "There are several ways to deal with vanishing or exploding gradients."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Normalization\n",
    "\n",
    "Normalization makes sure that in training, the size of the gradient does not get out of hand, because it is normalized by passing through this layer."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Residual Networks\n",
    "\n",
    "Residual networks reduces the depth of the networks by providing shortcuts. Shallower networks are less likely to have gradient explosion/vanishing problems."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Don't use certain activation functions\n",
    "\n",
    "Activation functions like `Sigmoid`, `Softmax`, `Tanh`, if applied over and over in several layers, will make the gradients of the network is extremely small. This is the reason `ReLU` is popular, because it doesn't suffer from gradient problems as often."
   ]
  }
 ],
 "metadata": {
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": 3
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
